package com.jie.server.mvc.service.impl;

import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.jie.server.core.ServerApplication;
import com.jie.server.mvc.mapper.FollowMapper;
import com.jie.server.mvc.mapper.UserMapper;
import com.jie.server.mvc.model.entity.Follow;
import com.jie.server.mvc.model.entity.User;
import com.jie.server.mvc.model.vo.FollowQueryVo;
import com.jie.server.mvc.model.vo.FollowUserVo;
import com.jie.server.mvc.service.FollowService;
import org.springframework.beans.BeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import java.util.*;

/**
 * <p>
 * 关注表 服务实现类
 * </p>
 *
 * @author XieZhiJie
 * @since 2022-04-24
 */
@Service
public class FollowServiceImpl extends ServiceImpl<FollowMapper, Follow> implements FollowService {

    private final FollowMapper followMapper;

    private final UserMapper userMapper;

    @Autowired
    public FollowServiceImpl(
            FollowMapper followMapper,
            UserMapper userMapper
    ) {
        this.followMapper = followMapper;
        this.userMapper = userMapper;
    }

    @Override
    public boolean add(Follow follow) {
        // 1.判断关注对象是否存在
        if (this.userMapper.selectById(follow.getOtherUserId()) == null || Objects.equals(follow.getUserId(), follow.getOtherUserId())) {
            return false;
        }
        // 2.判断是否已关注
        QueryWrapper<Follow> followQueryWrapper = new QueryWrapper<>();
        followQueryWrapper.eq("user_id", follow.getUserId());
        followQueryWrapper.eq("other_user_id", follow.getOtherUserId());
        if (this.followMapper.selectOne(followQueryWrapper) != null) {
            return false;
        }
        // 3.添加关注
        return this.followMapper.insert(follow) > 0;
    }

    @Override
    public Map<String, Object> getFollowUserList(Integer userId, FollowQueryVo followQueryVo) {
        // 1.查询出当前用户的关注列表
        QueryWrapper<Follow> followQueryWrapper = new QueryWrapper<>();
        followQueryWrapper.eq("user_id", userId);
        List<Follow> followList = this.followMapper.selectList(followQueryWrapper);
        QueryWrapper<User> userQueryWrapper = new QueryWrapper<>();
        Map<Integer, Follow> followMap = new HashMap<>(followList.size());
        if (followList.size() <= 0) {
            // 不可能的一个值
            userQueryWrapper.eq("user_id", -1);
        } else {
            List<Integer> followUserIdList = new ArrayList<>(followList.size());
            for (Follow follow : followList) {
                followUserIdList.add(follow.getOtherUserId());
                followMap.put(follow.getOtherUserId(), follow);
            }
            userQueryWrapper.in("user_id", followUserIdList);
            userQueryWrapper.select("user_id", "user_account", "username");
        }
        Page<User> page = new Page<>(followQueryVo.getCurrent(), followQueryVo.getLimit());
        this.userMapper.selectPage(page, userQueryWrapper);
        // 2.封装列表
        List<FollowUserVo> followUserVoList = new ArrayList<>(page.getRecords().size());
        for (User user : page.getRecords()) {
            FollowUserVo followUserVo = new FollowUserVo();
            BeanUtils.copyProperties(user, followUserVo);
            followUserVo.setRemark(followMap.get(user.getUserId()).getRemark());
            followUserVoList.add(followUserVo);
        }

        // 3.封装结果
        Map<String, Object> results = new HashMap<>(2);
        results.put("total", page.getTotal());
        results.put("records", followUserVoList);
        return results;
    }

    @Override
    public List<FollowUserVo> getOnlineFollowUserList(Integer userId) {
        // 1.获取关联
        QueryWrapper<Follow> followQueryWrapper = new QueryWrapper<>();
        followQueryWrapper.eq("user_id", userId);
        List<Follow> followList = this.followMapper.selectList(followQueryWrapper);
        // 2.获取在线的关注的用户id
        List<Integer> onlineUserIdList = new LinkedList<>();
        Map<Integer, Follow> followMap = new HashMap<>(followList.size());
        for (Follow follow : followList) {
            if (ServerApplication.SESSION.get(follow.getOtherUserId()) != null) {
                followMap.put(follow.getOtherUserId(), follow);
                onlineUserIdList.add(follow.getOtherUserId());
            }
        }
        List<User> userList;
        if (onlineUserIdList.size() <= 0) {
            userList = new LinkedList<>();
        } else {
            QueryWrapper<User> userQueryWrapper = new QueryWrapper<>();
            userQueryWrapper.in("user_id", onlineUserIdList);
            userList = this.userMapper.selectList(userQueryWrapper);
        }
        // 3.查询出来并封装
        List<FollowUserVo> followUserVoList = new ArrayList<>(userList.size());
        for (User user : userList) {
            FollowUserVo followUserVo = new FollowUserVo();
            BeanUtils.copyProperties(user, followUserVo);
            followUserVo.setRemark(followMap.get(user.getUserId()).getRemark());
            followUserVoList.add(followUserVo);
        }
        return followUserVoList;
    }

    @Override
    public boolean update(Follow follow) {
        // 1.查看关注信息是否存在
        String remark = follow.getRemark();
        if (follow.getOtherUserId() == null || remark == null || "".equals(remark.trim())) {
            return false;
        }
        QueryWrapper<Follow> followQueryWrapper = new QueryWrapper<>();
        followQueryWrapper.eq("user_id", follow.getUserId());
        followQueryWrapper.eq("other_user_id", follow.getOtherUserId());
        if ((follow = this.followMapper.selectOne(followQueryWrapper)) == null) {
            return false;
        }
        // 2.修改信息
        follow.setRemark(remark);
        return this.followMapper.updateById(follow) > 0;
    }

    @Override
    public List<User> getNotFollowUserList(Integer userId) {
        // 1.获取关联
        QueryWrapper<Follow> followQueryWrapper = new QueryWrapper<>();
        followQueryWrapper.eq("user_id", userId);
        List<Follow> followList = this.followMapper.selectList(followQueryWrapper);
        // 2.封装已关注列表
        List<Integer> followIdList = new ArrayList<>(followList.size() + 1);
        followIdList.add(userId);
        for (Follow follow : followList) {
            followIdList.add(follow.getOtherUserId());
        }
        // 3.查询未关注列表
        QueryWrapper<User> userQueryWrapper = new QueryWrapper<>();
        userQueryWrapper.notIn("user_id", followIdList);
        userQueryWrapper.select("user_id", "user_account", "username");
        return this.userMapper.selectList(userQueryWrapper);
    }

}
